package com.aaa.system.service.impl;

import com.aaa.entity.User;
import com.aaa.system.dao.MenuDao;
import com.aaa.system.dao.UserDao;
import com.aaa.system.service.MenuService;
import com.baomidou.mybatisplus.core.conditions.query.QueryWrapper;
import com.aaa.entity.Menu;
import com.aaa.utils.JWTUtils;
import com.aaa.utils.WebUtil;
import com.aaa.vo.Result;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.stereotype.Service;
import org.springframework.transaction.annotation.Transactional;
import org.springframework.util.StringUtils;

import javax.servlet.http.HttpServletRequest;
import java.util.*;
import java.util.stream.Collectors;

/**
 * @author Lei
 */
@Service
public class MenuServiceImpl implements MenuService {

    @Autowired
    private MenuDao menuDao;

    @Autowired
    private UserDao userDao;

    @Override
    public List<Menu> findByUserid(Long userId) {
        return menuDao.selectByuserid(userId);
    }

    @Override
    public Result<List<Menu>> getLeftMenu() {
        String token = WebUtil.getRequest().getHeader("token");
        Map<String, Object> info = JWTUtils.getInfo(token);
        String phone = (String) info.get("username");
        List<Menu> leftMenu = menuDao.getLeftMenu(phone);

        //查询所有的一级菜单
        List<Menu> firsts = leftMenu.stream().filter(item -> item.getParentId() == 0).collect(Collectors.toList());

        //查询所有的二级菜单-------适合只有两级菜单的情况
        // for (Menu f : firsts) {
        //     List<Menu> seconds = new ArrayList<>();
        //     for (Menu m : leftMenu) {
        //         if (m.getParentId().equals(f.getMenuId())){
        //             seconds.add(m);
        //         }
        //     }
        //     f.setChildren(seconds);
        // }


        //使用递归获取一级菜单下对应的二级菜单
        for (Menu f : firsts) {
            f.setChildren(getChildren(f.getMenuId(),leftMenu));
        }

        return new Result<>(200,"菜单请求成功",firsts);
    }

    @Override
    public Result<List<Menu>> getTreeAll() {
        QueryWrapper<Menu> queryWrapper = new QueryWrapper<>();
        queryWrapper.eq("status",0);
        List<Menu> menus = menuDao.selectList(queryWrapper);
        //查询所有的一级菜单
        List<Menu> firsts = menus.stream().filter(item -> item.getParentId() == 0).collect(Collectors.toList());
        //使用递归获取一级菜单下对应的二级菜单
        for (Menu f : firsts) {
            f.setChildren(getChildren(f.getMenuId(),menus));
        }
        return new Result<>(200,"树状菜单请求成功",firsts);
    }

    @Override
    public Result<List<Integer>> findByRoleId(Long roleId) {
        List<Integer> menuIds = menuDao.findByRoleId(roleId);
        return new Result<>(200,"查询当前角色菜单成功",menuIds);
    }

    @Transactional
    @Override
    public Result<List<Menu>> confirmMenu(Long roleId, Long[] menuIds) {
        //1、删除当前具有的角色菜单
        menuDao.deleteIds(roleId);

        //2、批量添加选中的角色菜单
        if (menuIds.length>0){
            menuDao.batchMenuIds(roleId,menuIds);
        }
        return new Result<>(200,"分配权限菜单成功");
    }

    @Override
    public Result<List<Menu>> selectAll(Menu menu) {
        QueryWrapper<Menu> queryWrapper = new QueryWrapper<>();
        if (StringUtils.hasText(menu.getMenuName())){
            queryWrapper.like("menu_name",menu.getMenuName());
        }
        if (Objects.nonNull(menu.getStatus())){
            queryWrapper.eq("status",menu.getStatus());
        }
        List<Menu> menus = menuDao.selectList(queryWrapper);

        //查询所有的一级菜单
        List<Menu> firsts = menus.stream().filter(item -> item.getParentId() == 0).collect(Collectors.toList());
        //使用递归获取一级菜单下对应的二级菜单
        for (Menu f : firsts) {
            f.setChildren(getChildren(f.getMenuId(),menus));
        }
        return new Result<>(200,"查询所有菜单成功",firsts);
    }

    @Override
    public Result<Boolean> saveOrUpdateMenu(Menu menu) {
        //直接在token获取手机号
        HttpServletRequest request = WebUtil.getRequest();
        String token = request.getHeader("token");
        Map<String, Object> tokenInfo = JWTUtils.getInfo(token);
        String phone = tokenInfo.get("username").toString();
        //通过token获取登录用户信息
        QueryWrapper<User> queryWrapper = new QueryWrapper<>();
        queryWrapper.eq("phone",phone);
        User userByToken = userDao.selectOne(queryWrapper);
        if (Objects.nonNull(menu.getMenuId())){
            //如果当前菜单对象有菜单id执行修改操作
            menu.setUpdateTime(new Date());
            menu.setUpdateBy(userByToken.getUserName());
            int i = menuDao.updateById(menu);
            return new Result<>(200,"修改菜单信息成功",i>0?true:false);
        }else {
            //如果当前菜单对象没有id就执行添加操作
            menu.setCreateTime(new Date());
            menu.setCreateBy(userByToken.getUserName());
            int insert = menuDao.insert(menu);
            return new Result<>(200,"添加菜单信息成功",insert>0?true:false);
        }
    }

    @Transactional
    @Override
    public Result<Boolean> deleteMenuByIds(Long menuId) {
        Boolean b = null;
        if (Objects.nonNull(menuId)){
            int i = menuDao.deleteById(menuId);
            menuDao.batchDelRoleMenu(menuId);
            b = true;
        }
        return new Result<>(200,"删除成功",b);
    }

    /**
     * 递归查询所有级别的菜单，并将下级菜单填入到上一级菜单的children中
     * @param parentId 菜单的父id
     * @param menus    所有的菜单数据
     * @return 菜单数组
     */
    private List<Menu> getChildren(Long parentId,List<Menu> menus){
        List<Menu> seconds = new ArrayList<>();
        for (Menu m : menus) {
            if (m.getParentId().equals(parentId)){
                seconds.add(m);
            }
        }

        //下一级菜单
        for (Menu m : seconds) {
            m.setChildren(getChildren(m.getMenuId(),menus));
        }
        return seconds;
    }
}
